package org.xtext.runtime.formula;

import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;

import org.xtext.runtime.term.Variable;
import org.xtext.runtime.util.Bindings;
import org.xtext.runtime.util.ILogicVisitor;



public class AND implements IFormula {
	private IFormula[] formulae;
	private Set<Variable> set = new HashSet<Variable>();
	
	public AND(IFormula[] formulae) {
		this.formulae = formulae;
		for (IFormula formula : formulae) {
			set.addAll(formula.variables());
		}
	}
	
	public IFormula[] formulae() {
		return formulae;
	}
	
	public String toString() {
		String output = "";
		for (int i=0;i<formulae.length; i++) {
			if (i > 0) output += " & ";
			output += formulae[i];
		}
		return output;
	}

	@Override
	public Set<Variable> variables() {
		return set;
	}

	@Override
	public IFormula apply(Bindings bindings) {
		for (IFormula formula : formulae) {
			formula.apply(bindings);
		}
		return this;
	}

	@Override
	public AND copy() {
		Map<String, Variable> vars = new HashMap<String, Variable>();
		IFormula[] temp = new IFormula[formulae.length];
		for (int i=0;i<formulae.length; i++) {
			temp[i] = formulae[i].copy(vars);
		}
		return new AND(temp);
	}

	@Override
	public AND copy(Map<String, Variable> vars) {
		IFormula[] temp = new IFormula[formulae.length];
		for (int i=0;i<formulae.length; i++) {
			temp[i] = formulae[i].copy(vars);
		}
		return new AND(temp);
	}

	@Override
	public boolean hasFreeVariables() {
		for (int i=0;i<formulae.length; i++) {
			if (formulae[i].hasFreeVariables()) return true;
		}
		return false;
	}

	@Override
	public Object accept(ILogicVisitor visitor) {
		return visitor.visit(this);
	}

	public int size() {
		return formulae.length;
	}

	public IFormula formulaAt(int i) {
		return formulae[i];
	}
}
